# Copyright (c) 2018 Presto Labs Pte. Ltd.
# Author: inkyu

from coin.strategy.cheese.pricer.sidecar.l2 import SidecarL2Pricer
from coin.exchange.shared.kr_rest.product import SharedCurrency
from scipy.stats.mstats import gmean


class SidecarL1Pricer(object):
  def __init__(self, *, specific_config, l1_config, strategy_logger):
    # key means the symbol of the base currency
    self._l1_config = l1_config
    self._l2_pricers = {}
    for key, l2_config in l1_config.items():
      self._l2_pricers[key] = SidecarL2Pricer(l2_config, strategy_logger=strategy_logger)
    self._pnl_calculator = None

  def set_pnl_calculator(self, pnl_calculator):
    self._pnl_calculator = pnl_calculator

  def available(self):
    return True

  def get_prices(self):
    return {key: self._l2_pricers[key].get_prices() for key in self._l2_pricers.keys()}

  def get_l2(self, key):
    return self._l2_pricers[key]

  def on_book(self, product, exchange_id, book, available):
    key = SharedCurrency.FromCurrency(product.base).currency
    self._l2_pricers[key].on_book(exchange_id, book, available)
    if exchange_id == 0 and self._pnl_calculator is not None:
      self._pnl_calculator.on_book(product, book)

  def on_trade(self, key, exchange_id, trade, available):
    self._l2_pricers[key].on_trade(exchange_id, trade, available)

  def _get_quote_value(self, premium):
    priority = ('USDT', 'PAX', 'USDC', 'TUSD', 'USD', 'USDK', 'HUSD')
    for usd_like_base in priority:
      if self._l1_config.quote_currencies[0] == usd_like_base:
        return 1.
      if self._l1_config.quote_currencies[1] == usd_like_base:
        return premium
    return None

  def update_quote_value(self, *, balance_printer):
    ema_prices = [self._l2_pricers[key].premium for key in self._l1_config.keys()]
    ema_prices = [ema_price for ema_price in ema_prices if ema_price is not None]
    if len(ema_prices) < 1:
      return
    quote_value = self._get_quote_value(gmean(ema_prices))
    if quote_value is not None:
      self._pnl_calculator.set_quote_value(quote_value)
    else:
      raise Exception('Not implemented')
